//
//  UILabel+Extentsion.swift
//  AJiTai
//
//  Created by BO ZHOU on 2020/5/10.
//  Copyright © 2020 BO ZHOU. All rights reserved.
//

import UIKit

/**
 * 本类中内边距都是采用将label先sizetoFit之后, 将其原本的frame按照内边距设置的值扩张得到的更大的frame
 * 并非真正意义的内边距
 * 所以在设置的时候可能cell会侵占到其他兄弟控件的frame, 自己设置的时候要控制好
 */

private var contentInset_key = "contentInset_key"

@IBDesignable public extension UILabel {

    /// 交换方法 并且只执行一次 程序已进入就执行交换
    public override class func initRunTime() {

        // 创建selector的两种方式
        // 交换setText方法
        // let sel = #selector(setter: UILabel.text)
        // let sel1 = Selector.init(("setText:"))

        // 交换setText方法
        exchange(originalSelector: #selector(setter: text), swizzledSelector: #selector(changeSetText(text:)))
        
        exchange(originalSelector: #selector(drawText(in:)), swizzledSelector: #selector(change_drawText(in:)))
        exchange(originalSelector: #selector(textRect(forBounds:limitedToNumberOfLines:)), swizzledSelector: #selector(change_textRect(forBounds:limitedToNumberOfLines:)))
    }

    // MARK: - 属性
    
    /**
     * 存储属性:
     * 给label扩充上下左右边距
     */
    var contentInset: UIEdgeInsets? {
        get {
            if let a = objc_getAssociatedObject(self, &contentInset_key) as? UIEdgeInsets {
                return a
            }
            return nil
        }
        set {
            
            // zwarning: OBJC_ASSOCIATION_ASSIGN 使用这个坑逼, 不能正确存储carType
            objc_setAssociatedObject(self, &contentInset_key, newValue, .OBJC_ASSOCIATION_RETAIN_NONATOMIC)
        }
    }
    
    
    /**
     * 计算属性:
     * 添加color_key, 格式 "#123456_0.40"
     */
    @IBInspectable var diy_textColor: String {
        get {
            return ""
        }
        set {
            self.textColor = colorWith(xibString: newValue) ?? UIColor.white
        }
    }
    
    /**
     * 计算属性:
     * 功能:
     * 给label扩充上下左右边距(xib用, 解析string)
     * 格式限定:     ① 1,2 (不要有空格, 上下, 左右), 给label上下内边距各为1, 左右内边距各为2
     *              ② 1,2,3,4 (上左下右), label上1, 左2, 下3, 右4
     */
    @IBInspectable var contentInsetString: String {
        get {
            return ""
        }
        set {
            
            let strings = (newValue as NSString).components(separatedBy: ",")

            if strings.count == 2 {
                
                // 格式1
                let paddingVertical = strings.first!.cgFloatValue
                let paddingHoriz = strings.last!.cgFloatValue
                
                contentInset = UIEdgeInsets(top: paddingVertical, left: paddingHoriz, bottom: paddingVertical, right: paddingHoriz)
            } else if strings.count == 4 {
                
                // 格式2
                let top = strings[0].cgFloatValue
                let left = strings[1].cgFloatValue
                let bottom = strings[2].cgFloatValue
                let right = strings[3].cgFloatValue
                
                contentInset = UIEdgeInsets(top: top, left: left, bottom: bottom, right: right)
            }
        }
    }

    
    /*
     * 方法交换: 给uilabel添加上下左右边距扩充
     */
    @objc func change_drawText(in rect: CGRect) {
        
        if let contentIn = contentInset {
            change_drawText(in: rect.inset(by: contentIn))
        } else {
            change_drawText(in: rect)
        }
    }

    /**
     * 方法交换: 给uilabel添加上下左右边距扩充
     */
    @objc func change_textRect(forBounds bounds: CGRect, limitedToNumberOfLines numberOfLines: Int) -> CGRect {
        
        if let contentIn = contentInset {

            var rect = change_textRect(forBounds: bounds.inset(by: contentIn),
                                      limitedToNumberOfLines: numberOfLines)
            rect.origin.x -= contentIn.left
            rect.origin.y -= contentIn.top
            rect.size.width += (contentIn.left + contentIn.right)
            rect.size.height += (contentIn.top + contentIn.bottom)
            return rect
        } else {
            return change_textRect(forBounds: bounds,
            limitedToNumberOfLines: numberOfLines)
        }
    }
    
    
    
    
    
    // MARK: 方法
         
    /*
     setText方法
     */
    @objc private func changeSetText(text: String) {
        
        changeSetText(text: text)
    }
    

}
